#include <everest/odbc/Environment.h>
#include <everest/odbc/SQLException.h>
#include <vector>
#include <string.h>
#include <stdio.h>

using namespace NS_EVEREST::odbc;
using namespace std;

struct DriverInfo::PData
{
	String          strDescription;
	vector<String>  vecAttribs;
};

DriverInfo::DriverInfo(const SQLCHAR *pszDesc, SQLSMALLINT desclen, const SQLCHAR *pAttribs, SQLSMALLINT attrlen)
	: m_pData(new PData)
{
	this->m_pData->strDescription = (pszDesc?(char *)pszDesc:"");
	m_pData->vecAttribs.reserve(64);
	const SQLCHAR *pStart = pAttribs;
	int count = 0;
	for (int i = 0; i < attrlen; ++i) {
		if ( pAttribs[i] == '\0') {
			String attrib;
			attrib.assign((const char *)pStart, count);
			m_pData->vecAttribs.push_back(attrib);
			pStart += (count + 1);
		} else {
			++count;
		}
	} // for
	return ;
}

DriverInfo::DriverInfo(const DriverInfo &drv)
	:m_pData(new PData)
{
	this->m_pData->strDescription = drv.m_pData->strDescription;
	this->m_pData->vecAttribs = drv.m_pData->vecAttribs;
	return ;
}

DriverInfo::~DriverInfo()
{
	if ( this->m_pData ) delete this->m_pData;
	this->m_pData = NULL;
	return ;
}

DriverInfo& DriverInfo::operator =(const DriverInfo& drvinfo)
{
	this->m_pData->strDescription = drvinfo.m_pData->strDescription;
	this->m_pData->vecAttribs = drvinfo.m_pData->vecAttribs;
	return *this;
}

const char * DriverInfo::getDescription() const
{
	return m_pData->strDescription.c_str();
}

int DriverInfo::getAttribCount() const
{
	return (int)m_pData->vecAttribs.size();
}

bool DriverInfo::getAttribute(int index, String& key, String& value) const
{
	if ( index < 0 || index > (int)m_pData->vecAttribs.size() ) return false;
	String& attrib = m_pData->vecAttribs[index];

	size_t pos = attrib.find_first_of('=');
	if ( pos == String::npos) {
		key = attrib;
	} else {
		key.assign(attrib.c_str(), pos);
		value.assign(attrib.c_str() + pos + 1);
	}
	return true;
}
